#nullable enable

//===================================================================
// 项目名 : Hbt.Cur
// 文件名 : HbtParallelNodeExecutor.cs
// 创建者 : Claude
// 创建时间: 2024-12-01
// 版本号 : V0.0.1
// 描述    : 工作流并行节点执行器
//===================================================================

using Hbt.Application.Services.Workflow.Engine.Parallel;
using Hbt.Application.Services.Workflow.Engine.Resolvers;

namespace Hbt.Application.Services.Workflow.Engine.Executors
{
    /// <summary>
    /// 工作流并行节点执行器
    /// </summary>
    public class HbtParallelNodeExecutor : HbtNodeExecutorBase
    {
        /// <summary>
        /// 并行工作流引擎
        /// </summary>
        private readonly IHbtParallelWorkflowEngine _parallelWorkflowEngine;

        /// <summary>
        /// 仓储工厂
        /// </summary>
        private readonly IHbtRepositoryFactory _repositoryFactory;

        /// <summary>
        /// 构造函数
        /// </summary>
        /// <param name="logger">日志服务</param>
        /// <param name="currentUser">当前用户服务</param>
        /// <param name="approverResolver">审批人解析器</param>
        /// <param name="parallelWorkflowEngine">并行工作流引擎</param>
        /// <param name="repositoryFactory">仓储工厂</param>
        public HbtParallelNodeExecutor(
            IHbtLogger logger,
            IHbtCurrentUser currentUser,
            IHbtApproverResolver approverResolver,
            IHbtParallelWorkflowEngine parallelWorkflowEngine,
            IHbtRepositoryFactory repositoryFactory) : base(logger, currentUser, approverResolver)
        {
            _parallelWorkflowEngine = parallelWorkflowEngine ?? throw new ArgumentNullException(nameof(parallelWorkflowEngine));
            _repositoryFactory = repositoryFactory ?? throw new ArgumentNullException(nameof(repositoryFactory));
        }

        /// <inheritdoc/>
        public override bool CanHandle(string nodeType)
        {
            return nodeType.Equals("parallel", StringComparison.OrdinalIgnoreCase);
        }

        /// <inheritdoc/>
        public override string GetNodeTypeDescription(string nodeType)
        {
            return "并行节点";
        }

        /// <inheritdoc/>
        public override async Task<HbtApproveResult> ExecuteAsync(
            long instanceId,
            string nodeId,
            string nodeType,
            string? nodeConfig,
            Dictionary<string, object>? variables = null)
        {
            try
            {
                LogNodeExecution(instanceId, nodeId, "开始执行并行节点");

                // 解析并行节点配置
                if (string.IsNullOrEmpty(nodeConfig))
                {
                    throw new InvalidOperationException("并行节点配置不能为空");
                }

                var parallelConfig = JsonConvert.DeserializeObject<HbtParallelBranchConfigDto>(nodeConfig);
                if (parallelConfig == null || !parallelConfig.Branches.Any())
                {
                    throw new InvalidOperationException("并行节点配置无效");
                }

                // 创建并行分支
                var branchInstanceIds = await _parallelWorkflowEngine.CreateParallelBranchesAsync(instanceId, parallelConfig);

                // 记录并行分支创建操作
                await RecordParallelOperationAsync(instanceId, nodeId, "创建并行分支",
                    $"成功创建 {branchInstanceIds.Count} 个并行分支");

                LogNodeExecution(instanceId, nodeId, $"并行节点执行完成，创建了 {branchInstanceIds.Count} 个分支");

                return CreateSuccessResult(
                    nextNodeId: null, // 并行节点不直接流转到下一个节点，需要等待分支汇聚
                    nextNodeName: null,
                    workflowStatus: 5); // 5 表示并行执行中
            }
            catch (Exception ex)
            {
                LogNodeError(instanceId, nodeId, ex);
                return CreateFailureResult($"并行节点执行失败: {ex.Message}");
            }
        }

        /// <summary>
        /// 记录并行操作
        /// </summary>
        private async Task RecordParallelOperationAsync(long instanceId, string nodeId, string operation, string remark)
        {
            try
            {
                var operRecord = new HbtInstanceOper
                {
                    InstanceId = instanceId,
                    NodeId = nodeId,
                    NodeName = "并行节点",
                    OperType = 9, // 9 表示并行操作
                    OperatorId = _currentUser.UserId,
                    OperatorName = _currentUser.UserName,
                    OperOpinion = $"{operation}: {remark}",
                    CreateTime = DateTime.Now
                };

                await GetOperRepository().CreateAsync(operRecord);
            }
            catch (Exception ex)
            {
                _logger.Error($"记录并行操作失败: {ex.Message}", ex);
            }
        }

        /// <summary>
        /// 获取操作记录仓储
        /// </summary>
        private IHbtRepository<HbtInstanceOper> GetOperRepository()
        {
            return _repositoryFactory.GetWorkflowRepository<HbtInstanceOper>();
        }
    }
}